// Native
import { join } from "path";

// Packages
import {
  Menu,
  BrowserWindow,
  app,
  ipcMain,
  IpcMainEvent,
  screen,
  Tray,
} from "electron";
import isDev from "electron-is-dev";
import path from "node:path";
import store from "./store";
import createAddStockWindow from "./AddStockWindow";

let tray: Tray | null = null;
// const p = path.join("/resources", "1.png");
// const icon = nativeImage.createFromPath(p);

const icon = isDev
  ? path.resolve("resources/icon.ico")
  : path.resolve("resources/resources/icon.ico");

function createWindow() {
  // Create the browser window.
  const window = new BrowserWindow({
    icon,
    width: 120,
    height: 120,
    type: "toolbar", // 创建的窗口类型为工具栏窗口
    frame: false, // 要创建无边框窗口
    resizable: false, // 禁止窗口大小缩放
    transparent: true, // 设置透明
    alwaysOnTop: true, // 窗口是否总是显示在其他窗口之前
    webPreferences: {
      nodeIntegration: true, // 是否集成node
      contextIsolation: true, // 是否上下文隔离
      preload: path.join(__dirname, "./preload.js"), // 通过预加载将 electron 中的一些 node 的API挂载到window对象上
      webSecurity: false,
    },
  });

  // 通过获取用户屏幕的宽高来设置悬浮球的初始位置
  const { left, top } = {
    left: screen.getPrimaryDisplay().workAreaSize.width - 160,
    top: screen.getPrimaryDisplay().workAreaSize.height - 160,
  };
  window.setPosition(left, top); // 设置悬浮球位置

  const port = process.env.PORT || 3000;
  const url = isDev
    ? `http://localhost:${port}`
    : join(__dirname, "../src/out/index.html");

  // and load the index.html of the app.
  if (isDev) {
    window?.loadURL(url);
  } else {
    window?.loadFile(url);
  }
  // Open the DevTools.
  // window.webContents.openDevTools();

  ipcMain.on("suspensionWindowMove", (_event, message) => {
    window.setPosition(message.x, message.y);
  });

  // For AppBar
  ipcMain.on("minimize", () => {
    // eslint-disable-next-line no-unused-expressions
    window.isMinimized() ? window.restore() : window.minimize();
    // or alternatively: win.isVisible() ? win.hide() : win.show()
  });
  ipcMain.on("maximize", () => {
    // eslint-disable-next-line no-unused-expressions
    window.isMaximized() ? window.restore() : window.maximize();
  });

  ipcMain.on("close", () => {
    window.close();
  });

  // 禁止窗口最大化
  window.setMaxListeners(1);
}

function createTray() {
  // 创建一个原生图像对象，这里使用PNG格式的图标示例

  // 创建托盘实例
  tray = new Tray(icon);

  // 创建上下文菜单
  const contextMenu = Menu.buildFromTemplate([
    { label: "添加龙股", click: createAddStockWindow },
    { label: "打开应用", click: createWindow },
    { label: "退出", click: () => app.quit() },
  ]);

  // 设置托盘的上下文菜单
  tray.setContextMenu(contextMenu);

  // 设置托盘提示信息
  tray.setToolTip("股海擒龙");

  tray.on("click", () => {
    createWindow();
  });
  // // 监听托盘销毁事件
  // tray.on("destroyed", () => {
  //   tray = null;
  // });
}
// This method will be called when Electron has finished
// initialization and is ready to create browser windows.
// Some APIs can only be used after this event occurs.
app.whenReady().then(() => {
  createWindow();
  createTray();

  app.on("activate", () => {
    // On macOS it's common to re-create a window in the app when the
    // dock icon is clicked and there are no other windows open.
    if (BrowserWindow.getAllWindows().length === 0) createWindow();
  });
});

// Quit when all windows are closed, except on macOS. There, it's common
// for applications and their menu bar to stay active until the user quits
// explicitly with Cmd + Q.
app.on("window-all-closed", () => {
  if (process.platform !== "darwin") app.quit();
});

// In this file you can include the rest of your app's specific main process
// code. You can also put them in separate files and require them here.

// listen the channel `message` and resend the received message to the renderer process
ipcMain.on("message", (event: IpcMainEvent, message: any) => {
  console.log(message);
  setTimeout(() => event.sender.send("message", "hi from electron"), 500);
});

ipcMain.on("getStocks", (event: IpcMainEvent) => {
  // eslint-disable-next-line no-param-reassign,no-console
  // eslint-disable-next-line no-param-reassign
  const stocks = store.get("stocks") as unknown as string[];
  console.log("getStocks");
  console.log(stocks);
  if (!stocks) {
    event.returnValue = [];
    return;
  }
  event.returnValue = stocks;
});

ipcMain.on("hideMainWindow", (_event: IpcMainEvent) => {
  BrowserWindow.getFocusedWindow()?.hide();
});
ipcMain.on("addStock", (event: IpcMainEvent, stockCode: string) => {
  // eslint-disable-next-line @typescript-eslint/ban-ts-comment
  // @ts-ignore
  if (!stockCode) return;
  const stocks = store.get("stocks") as unknown as string[];
  if (!stocks) {
    store.set("stocks", [stockCode]);
    return;
  }
  if (!stocks.includes(stockCode)) {
    store.set("stocks", [...stocks, stockCode]);
  }
  // eslint-disable-next-line no-param-reassign
  event.returnValue = store.get("stocks");
});

ipcMain.on("delStock", (event: IpcMainEvent, stockCode: string) => {
  // eslint-disable-next-line @typescript-eslint/ban-ts-comment
  // @ts-ignore
  store.set(
    "stocks",
    (store.get("stocks") as unknown as string[]).filter(
      (item) => item !== stockCode
    )
  );
  const stocks = store.get("stocks") as unknown as string[];
  // eslint-disable-next-line no-param-reassign
  if (!stocks) {
    event.returnValue = [];
    return;
  }
  event.returnValue = stocks;
});

ipcMain.on("closeAddStockWindow", (_event: IpcMainEvent) => {
  BrowserWindow.getFocusedWindow()?.hide();
});
